<!DOCTYPE html>
<html>

<head>
  <meta charset="utf-8">
  <title>贪吃蛇</title>
  <style type="text/css">
    * {
      margin: 0;
      padding: 0;
    }

    ul,
    li {
      list-style: none;
    }

    img {
      border: 0px;
    }

    #main {
      width: 800px;
      height: 450px;
      margin: 50px auto;
    }

    #map {
      width: 800px;
      height: 400px;
      background: url(img/bj.jpg);
      position: relative;
    }

    button {
      width: 100px;
      height: 50px;
    }
  </style>
</head>

<body>
  <div id="main">
    <button type="button">开始游戏</button>
    <div id="map"></div>
  </div>
</body>

</html>
<script type="text/javascript">
  //创建蛇对象
  function Snake() {
    this.fx = 'y';
    this.w = 20;
    this.h = 20;
    this.body = [
      { x: 2, y: 0 },
      { x: 1, y: 0 },
      { x: 0, y: 0 }
    ];
    this.display = function () {
      for (var i = 0; i < this.body.length; i++) {
        var oimg = document.createElement('img');

        this.body[i].flag = oimg;

        oimg.src = 'img/s.jpg';

        oimg.style.width = this.w + 'px';
        oimg.style.height = this.h + 'px';

        oimg.style.position = 'absolute';
        oimg.style.left = this.body[i].x * this.w + 'px';
        oimg.style.top = this.body[i].y * this.h + 'px';

        document.getElementById('map').appendChild(oimg);
      }
    }
    //让蛇跑
    this.run = function () {
      for (var i = this.body.length - 1; i > 0; i--) {
        this.body[i].x = this.body[i - 1].x;
        this.body[i].y = this.body[i - 1].y;
      }
      switch (this.fx) {
        case 'y': this.body[0].x += 1; break;
        case 'z': this.body[0].x -= 1; break;
        case 's': this.body[0].y -= 1; break;
        case 'x': this.body[0].y += 1; break;
      }
      //限制范围，碰墙游戏结束
      if (this.body[0].x < 0 || this.body[0].x > 39 || this.body[0].y < 0 || this.body[0].y > 19) {
        clearInterval(timer);
        alert('游戏结束 GAME OVER!!');
        return false;
      }

      //吃到自己结束游戏
      for (var i = 4; i < this.body.length; i++) {
        if (this.body[0].x == this.body[i].x && this.body[0].y == this.body[i].y) {
          clearInterval(timer);
          alert('吃货，连自己都不放过...');
          return false;
        }
      }
      //清除以前的蛇
      for (var i = 0; i < this.body.length; i++) {
        if (this.body[i].flag != null) {
          document.getElementById('map').removeChild(this.body[i].flag);
        }
      }
      this.display();
      //蛇吃到食物增加一节
      if (this.body[0].x == food.x && this.body[0].y == food.y) {
        this.body.push({ x: null, y: null, flag: null });
        //让食物刷新
        document.getElementById('map').removeChild(food.flag);
        food.display();
      }
    }
  }
  //创建食物对象
  function Food() {
    this.w = 20;
    this.h = 20;
    this.display = function () {
      var oimg = document.createElement('img');
      this.flag = oimg;
      oimg.src = "img/sw.jpg";

      oimg.style.width = this.w + 'px';
      oimg.style.height = this.h + 'px';

      this.x = Math.floor(Math.random() * 40);
      this.y = Math.floor(Math.random() * 20);

      oimg.style.position = 'absolute';
      oimg.style.left = this.x * this.w + 'px';
      oimg.style.top = this.y * this.h + 'px';

      document.getElementById('map').appendChild(oimg);
    }
  }
  //实例化蛇对象
  var snake = new Snake();
  snake.display();
  //实例化食物对象
  var food = new Food();
  food.display();

  var oBtn = document.getElementsByTagName('button');
  var timer = null;
  //实现按钮的功能
  oBtn[0].onclick = function () {
    clearInterval(timer);
    timer = setInterval("snake.run()", 250);
  }
  //通过按键改变蛇的方向
  document.body.onkeydown = function (e) {
    var ev = e || window.event;
    switch (ev.keyCode) {
      case 37:
        if (snake.fx != 'y') {
          snake.fx = 'z';
        }
        break;
      case 38:
        if (snake.fx != 'x') {
          snake.fx = 's';
        }
        break;
      case 39:
        if (snake.fx != 'z') {
          snake.fx = 'y';
        }
        break;
      case 40:
        if (snake.fx != 's') {
          snake.fx = 'x';
        }
        break;
    }
  }
</script>